package com.ashlikun.pdfview.renderer

import android.content.Context
import android.graphics.Bitmap
import android.graphics.RectF
import android.util.Size
import com.ashlikun.pdfview.PDFViewConfig
import com.ashlikun.pdfview.model.PdfBookmark
import com.ashlikun.pdfview.model.PdfLink
import com.ashlikun.pdfview.model.PdfMeta
import com.ashlikun.pdfview.source.DocumentSource
import com.ashlikun.pdfview.util.PdfViewUtil
import com.shockwave.pdfium.PdfDocument
import com.shockwave.pdfium.PdfDocument.Bookmark
import com.shockwave.pdfium.PdfiumCore
import java.io.IOException

/**
 * 作者　　: 李坤
 * 创建时间: 2024/7/3　13:15
 * 邮箱　　：496546144@qq.com
 *
 *
 * 功能介绍：第三方库 com.github.barteksc:pdfium-android:1.9.0
 */
class PdfiumRenderer(private val context: Context, private val config: PDFViewConfig) : IPdfRenderer {
    /**
     * 用于加载和渲染PDF的Pdfium内核
     */
    @JvmField
    var pdfiumCore: PdfiumCore
    private var pdfDocument: PdfDocument? = null

    init {
        pdfiumCore = PdfiumCore(context)
    }

    @Throws(IOException::class)
    override fun createRenderer(docSource: DocumentSource, password: String?) {
        pdfDocument = docSource!!.create(context, this, password) as PdfDocument
    }

    override fun renderPage(bitmap: Bitmap, pageIndex: Int, width: Int, height: Int, annotationRendering: Boolean) {
        if (PdfViewUtil.DEBUG_MODE) PdfViewUtil.logi("renderPage start pageIndex = " + pageIndex + "  width = " + bitmap!!.width + "    height" + bitmap.height)
        pdfiumCore.renderPageBitmap(pdfDocument, bitmap, pageIndex, 0, 0, width, height, annotationRendering)
        if (PdfViewUtil.DEBUG_MODE) PdfViewUtil.logi("renderPage end pageIndex = $pageIndex")
    }

    override val pageCount: Int
        get() = pdfiumCore.getPageCount(pdfDocument)

    override fun getPageSize(pageIndex: Int): Size {
        val size = pdfiumCore.getPageSize(pdfDocument, pageIndex)
        var width = size.width
        var height = size.height
        val size2 = Size(width, height)
        if (PdfViewUtil.DEBUG_MODE) PdfViewUtil.logi("getPageSize   pageIndex = " + pageIndex + "  width = " + size2.width + "    height" + size2.height)
        return size2
    }

    override fun openPage(pageIndex: Int) {
        pdfiumCore.openPage(pdfDocument, pageIndex)
    }

    override val metaData: PdfMeta
        get() {
            val meta = pdfiumCore.getDocumentMeta(pdfDocument)
            val pdfMeta = PdfMeta()
            pdfMeta.title = meta.title
            pdfMeta.author = meta.author
            pdfMeta.subject = meta.subject
            pdfMeta.keywords = meta.keywords
            pdfMeta.creator = meta.creator
            pdfMeta.producer = meta.producer
            pdfMeta.creationDate = meta.creationDate
            pdfMeta.modDate = meta.modDate
            return pdfMeta
        }

    private fun getBookmarks2(bookmarks: List<Bookmark>?): List<PdfBookmark> {
        val pdfBookmarks = ArrayList<PdfBookmark>()
        bookmarks?.forEach { pi ->
            val item = PdfBookmark()
            item.title = pi.title
            item.pageIdx = pi.pageIdx
            if (pi.hasChildren()) {
                item.children = getBookmarks2(pi.children)
            }
            pdfBookmarks.add(item)
        }
        return pdfBookmarks
    }

    override val bookmarks: List<PdfBookmark>
        get() {
            val bookmarks = pdfiumCore.getTableOfContents(pdfDocument)
            return getBookmarks2(bookmarks)
        }

    override fun getPageLinks(docPage: Int): List<PdfLink> {
        val links = pdfiumCore.getPageLinks(pdfDocument, docPage)
        //数组转换
        val pdfLinks = ArrayList<PdfLink>()
        links?.forEach {
            val item = PdfLink(it.bounds, it.destPageIdx, it.uri)
            pdfLinks.add(item)
        }
        return pdfLinks
    }

    override fun mapRectToDevice(docPage: Int, startX: Int, startY: Int, sizeX: Int, sizeY: Int, i: Int, rect: RectF): RectF {
        return pdfiumCore.mapRectToDevice(pdfDocument, docPage, startX, startY, sizeX, sizeY, i, rect)
    }

    override fun close() {
        pdfiumCore.closeDocument(pdfDocument)
    }
}
